﻿@using Cropper.Blazor.Models;
@using Cropper.Blazor.Components

@inject IJSRuntime JS;

<link href="_content/Cropper.Blazor/cropper.min.css" rel="stylesheet" />
<script src="_content/Cropper.Blazor/cropper.min.js"></script>

<RadzenCard>
    <div style=@("object-fit: fill !important;  position: relative; overflow: hidden; "+"width:"+(ContainerBoxWidth+"px")+";height:"+(ContainerBoxHeight+"px"))>
        <CropperComponent Src="@ImageUrl" @ref="CropperComponent" Options="CropperOptions" />
    </div>

    <RadzenSelectBar Value="@ViewMode" TValue="ViewMode" ValueChanged="@ViewModeValueChanged" TextProperty="Text" ValueProperty="Value" Data="@(Enum.GetValues(typeof(ViewMode)).Cast<ViewMode>().Select(t => new { Text = $"{t}", Value = t }))" Size="ButtonSize.Small" class="rz-display-none rz-display-xl-flex" />
    <RadzenButton Icon="check" title="Crop" Click="@CropperOkChange"></RadzenButton>
    <RadzenButton Icon="filter" Click="@GetCropImageClick">Get</RadzenButton>
</RadzenCard>

@code {
    private CropImageData Data { get; set; }
    public ViewMode ViewMode = ViewMode.Vm3;

    [Parameter]
    public string ImageUrl { get; set; }

    [Parameter]
    public int ContainerBoxWidth { get; set; } = 400;

    [Parameter]
    public int ContainerBoxHeight { get; set; } = 400;

    [CascadingParameter]
    private Radzen.Dialog _dialog { get; set; }

    [Inject]
    private Radzen.DialogService _dialogService { get; set; }

    protected override async Task OnInitializedAsync()
    {

    }


    private async Task CropperOkChange()
    {
        var cropData = await GetCropOffsetWithRotation();
        //var cropData = await CropperComponent.GetCropBoxDataAsync();
        ImageReceiver imageReceiver = await CropperComponent.GetCroppedCanvasDataInBackgroundAsync(new GetCroppedCanvasOptions() { MaxHeight = 4096, MaxWidth = 4096 });
        InvokeAsync(async () =>
        {
            using MemoryStream croppedCanvasDataStream = await imageReceiver.GetImageChunkStreamAsync();
            byte[] croppedCanvasData = croppedCanvasDataStream.ToArray();
            if (croppedCanvasData != null && croppedCanvasData.Length > 0)
            {
                CropImageData data = new CropImageData();
                data.StartX = cropData.X;
                data.StartY = cropData.Y;
                data.Width = cropData.Width;
                data.Height = cropData.Height;
                data.ImageUrl = "data:image/png;base64," + Convert.ToBase64String(croppedCanvasData);
                data.ImageBytes = croppedCanvasData;
                _dialogService.Close(data); // 明确返回当前Data值
            }
        });
    }

    /// <summary>
    /// 获取裁剪区域相对于原始图像的准确偏移量和尺寸
    /// </summary>
    /// <returns></returns>
    private async Task<ImageOffset> GetCropOffsetWithRotation()
    {
        var cropBoxData = await CropperComponent.GetCropBoxDataAsync();
        var imageData = await CropperComponent.GetImageDataAsync();
        var canvasData = await CropperComponent.GetCanvasDataAsync();

        var scaleX = imageData.NaturalWidth / imageData.Width;
        var scaleY = imageData.NaturalHeight / imageData.Height;

        // 简单情况下仍然可以使用之前的计算方法
        return new ImageOffset
        {
            X = (cropBoxData.Left - canvasData.Left) * scaleX,
            Y = (cropBoxData.Top - canvasData.Top) * scaleY,
            Width = cropBoxData.Width * scaleX,
            Height = cropBoxData.Height * scaleY
        };
    }

    public class ImageOffset
    {
        public decimal X { get; set; }
        public decimal Y { get; set; }
        public decimal Width { get; set; }
        public decimal Height { get; set; }
    }

    private async Task ViewModeValueChanged(ViewMode value)
    {
        ViewMode = value;
        CropperOptions.ViewMode = value;
        CropperComponent?.InitCropper();
        CropperComponent?.Destroy();
        CropperComponent?.InitCropper();
    }


    private CropperComponent? CropperComponent = null!;

    protected override async Task OnAfterRenderAsync(bool firstRender)
    {
        if (firstRender)
        {
        }
    }

    // Setting up initial dimensions of crop area
    private Options CropperOptions = new Options
    {
        SetDataOptions = new SetDataOptions
        {
        },
        ViewMode = ViewMode.Vm3,
        AutoCropArea = (decimal)0.5, // 裁剪区域占图片50%
        Responsive = true,
        Restore = false,
        CheckCrossOrigin = false
    };


    public string CropImageUrl { get; set; }
    private async Task GetCropImageClick()
    {
        ImageReceiver imageReceiver = await CropperComponent.GetCroppedCanvasDataInBackgroundAsync(new GetCroppedCanvasOptions() { MaxHeight = 4096, MaxWidth = 4096 });
        using MemoryStream croppedCanvasDataStream = await imageReceiver.GetImageChunkStreamAsync();
        byte[] croppedCanvasData = croppedCanvasDataStream.ToArray();
        if (croppedCanvasData != null && croppedCanvasData.Length > 0)
        {
            CropImageUrl = "data:image/png;base64," + Convert.ToBase64String(croppedCanvasData);

        }
        var result = await _dialogService.OpenAsync("Cropped Image", ds =>
        @<RadzenStack Gap="1.5rem">
            <RadzenImage Path="@CropImageUrl">

            </RadzenImage>
        </RadzenStack>);
}

}
